package com.cc.mydlnademo

import android.content.Context
import android.provider.MediaStore
import android.provider.MediaStore.Audio.Media
import android.util.Log
import androidx.core.database.getIntOrNull
import androidx.core.database.getStringOrNull

const val AUDIO_SUFFIX = "_audio.mp3"
const val VIDEO_SUFFIX = "_video.mp4"

data class VideoData(
    var title: String,
    var path: String,
    var size: Int,
    var type: String,
    var _id: String,
    var diration: Int
) {
    fun getPlayItem(): String {
        return "${_id}${VIDEO_SUFFIX}"
    }
}

class AudioData(
    val title: String,
    val path: String,
    var artist: String,
    var album: String,
    val _id: String,
    var size: Int
) {
    fun getPlayItem(): String {
        return "${_id}${AUDIO_SUFFIX}"
    }
}

fun AudioData.createDlnaItem(ip: String): String {
    return "<?xml version=\"1.0\" encoding=\"utf-8\"?>" +
            "<DIDL-Lite xmlns=\"urn:schemas-upnp-org:metadata-1-0/DIDL-Lite/\" xmlns:upnp=\"urn:schemas-upnp-org:metadata-1-0/upnp/\" xmlns:dc=\"http://purl.org/dc/elements/1.1/\" xmlns:sec=\"http://www.sec.co.kr/\">" +
            "<item id=\"$_id\" parentID=\"2\" restricted=\"0\">" +
            "<dc:title>${title.checkValue()}</dc:title>" +
            "<dc:creator>${artist.checkValue()}</dc:creator>" +
            "<upnp:class>${javaClass.name}k</upnp:class>" +
            "<upnp:album>${album.checkValue()}</upnp:album>" +
            "<upnp:artist role=\"Performer\">${artist.checkValue()}</upnp:artist>" +
            "<res protocolInfo=\"http-get:*:${getMimeType(path)}:*\" size=\"${size}\" duration=\"00:04:08\">$ip/${_id}_audio.mp3</res>" +
            "</item>" +
            "</DIDL-Lite>"
}

private fun String.checkValue(): String {
    return replace("<", "").replace(">", "")
}

fun getMimeType(url: String): String {
    val array = url.split(".")
    var type = ""
    if (array.size > 1) {
        type = array.last()
    }
    if (type.equals("mp3", true)) {
        return "audio/mpeg"
    } else if (type.equals("wav", true)) {
        return "audio/x-wav"
    } else if (type.equals("flac", true)) {
        return "audio/flac"
    } else if (type.equals("avi", true)) {
        return "video/x-msvideo"
    } else if ("mp4\\mpg4\\m4v\\mp4v".contains(type, true)) {
        return "video/mp4"
    }
    return url
}


private const val TAG = "MediaProvider"
fun Context.getLocalVideo(): MutableList<VideoData> {
    val cursor = contentResolver.query(
        MediaStore.Video.Media.EXTERNAL_CONTENT_URI,
        null,
        null,
        null,
        null,
        null
    )
    val mutableList = mutableListOf<VideoData>()
    cursor?.run {
        while (moveToNext()) {
            val path = getStringOrNull(getColumnIndex(MediaStore.Video.VideoColumns.DATA)) ?: ""
            val name =
                getStringOrNull(getColumnIndex(MediaStore.Video.VideoColumns.DISPLAY_NAME)) ?: ""
            val size = getIntOrNull(getColumnIndex(MediaStore.Video.VideoColumns.SIZE)) ?: 0
            val type =
                getStringOrNull(getColumnIndex(MediaStore.Video.VideoColumns.MIME_TYPE)) ?: ""
            val _id = getStringOrNull(getColumnIndex(MediaStore.Video.VideoColumns._ID)) ?: ""
            val duration = getIntOrNull(getColumnIndex(MediaStore.Video.VideoColumns.DURATION)) ?: 0
            if (size == 0) {
                continue
            }
            val videoData = VideoData(name, path, size, type, _id,duration)
            Log.i(TAG, videoData.toString())
            mutableList.add(videoData)
        }
    }
    return mutableList
}

fun Context.getLocalAudio(): MutableList<AudioData> {
    val mutableList = mutableListOf<AudioData>()
    val cursor = contentResolver.query(
        MediaStore.Audio.Media.EXTERNAL_CONTENT_URI,
        arrayOf(
            MediaStore.Audio.AudioColumns.TITLE,
            MediaStore.Audio.AudioColumns.DATA,
            MediaStore.Audio.AudioColumns.ALBUM,
            MediaStore.Audio.AudioColumns.ARTIST,
            MediaStore.Audio.AudioColumns.SIZE,
            MediaStore.Audio.AudioColumns._ID
        ),
        null,
        null,
        null,
        null
    )
    cursor?.run {
        while (moveToNext()) {
            val path = getStringOrNull(getColumnIndex(MediaStore.Audio.AudioColumns.DATA)) ?: ""
            val title =
                getStringOrNull(getColumnIndex(MediaStore.Audio.AudioColumns.TITLE)) ?: ""
            val artist =
                getStringOrNull(getColumnIndex(MediaStore.Audio.AudioColumns.ARTIST)) ?: ""

            val album =
                getStringOrNull(getColumnIndex(MediaStore.Audio.AudioColumns.ARTIST)) ?: ""
            val size = getInt(getColumnIndex(MediaStore.Audio.AudioColumns.SIZE)) ?: 0
            val _id = getStringOrNull(getColumnIndex(MediaStore.Audio.AudioColumns._ID)) ?: ""
            if (size < 1024) {
                continue
            }
            val audioData = AudioData(title, path, artist, album, _id, size)
            Log.i(TAG, audioData.toString())
            mutableList.add(audioData)
        }
    }
    return mutableList
}

fun Context.getLocalAudioById(_id: String): AudioData? {
    val cursor = contentResolver.query(
        MediaStore.Audio.Media.EXTERNAL_CONTENT_URI,
        null,
        "${MediaStore.Audio.AudioColumns._ID} = ?",
        arrayOf(_id),
        null,
        null
    )
    cursor?.run {
        while (moveToFirst()) {
            val path = getStringOrNull(getColumnIndex(MediaStore.Audio.AudioColumns.DATA)) ?: ""
            val title =
                getStringOrNull(getColumnIndex(MediaStore.Audio.AudioColumns.TITLE)) ?: ""
            val artist =
                getStringOrNull(getColumnIndex(MediaStore.Audio.AudioColumns.ARTIST)) ?: ""

            val album =
                getStringOrNull(getColumnIndex(MediaStore.Audio.AudioColumns.ARTIST)) ?: ""
            val size = getInt(getColumnIndex(MediaStore.Audio.AudioColumns.SIZE)) ?: 0
            val _id = getStringOrNull(getColumnIndex(MediaStore.Audio.AudioColumns._ID)) ?: ""
            if (size < 1024) {
                continue
            }
            return AudioData(title, path, artist, album, _id, size)

        }
    }
    return null
}

fun Context.getLocalVideoById(_id: String): VideoData? {
    val cursor = contentResolver.query(
        MediaStore.Video.Media.EXTERNAL_CONTENT_URI,
        arrayOf(
            MediaStore.Video.VideoColumns.DATA,
            MediaStore.Video.VideoColumns.DISPLAY_NAME,
            MediaStore.Video.VideoColumns.SIZE,
            MediaStore.Video.VideoColumns.MIME_TYPE,
            MediaStore.Video.VideoColumns._ID
        ),
        "${MediaStore.Video.VideoColumns._ID} = ?",
        arrayOf(_id),
        null,
        null
    )
    cursor?.run {
        while (moveToFirst()) {
            val path = getStringOrNull(getColumnIndex(MediaStore.Video.VideoColumns.DATA)) ?: ""
            val name =
                getStringOrNull(getColumnIndex(MediaStore.Video.VideoColumns.DISPLAY_NAME)) ?: ""
            val size = getIntOrNull(getColumnIndex(MediaStore.Video.VideoColumns.SIZE)) ?: 0
            val type =
                getStringOrNull(getColumnIndex(MediaStore.Video.VideoColumns.MIME_TYPE)) ?: ""
            val _id = getStringOrNull(getColumnIndex(MediaStore.Video.VideoColumns._ID)) ?: ""
            val duration = getIntOrNull(getColumnIndex(MediaStore.Video.VideoColumns.DURATION)) ?: 0
            if (size == 0) {
                continue
            }
            val videoData = VideoData(name, path, size, type, _id,duration)
            Log.i(TAG, videoData.toString())
            return videoData
        }
    }
    return null
}

fun Context.getLocalVideoByPath(path: String): VideoData? {
    val cursor = contentResolver.query(
        MediaStore.Video.Media.EXTERNAL_CONTENT_URI,
        arrayOf(
            MediaStore.Video.VideoColumns.DATA,
            MediaStore.Video.VideoColumns.DISPLAY_NAME,
            MediaStore.Video.VideoColumns.SIZE,
            MediaStore.Video.VideoColumns.MIME_TYPE,
            MediaStore.Video.VideoColumns._ID,
            MediaStore.Video.VideoColumns.DURATION
        ),
        "${MediaStore.Video.VideoColumns.DATA} = ?",
        arrayOf(path),
        null,
        null
    )
    cursor?.run {
        while (moveToFirst()) {
            val path = getStringOrNull(getColumnIndex(MediaStore.Video.VideoColumns.DATA)) ?: ""
            val name =
                getStringOrNull(getColumnIndex(MediaStore.Video.VideoColumns.DISPLAY_NAME)) ?: ""
            val size = getIntOrNull(getColumnIndex(MediaStore.Video.VideoColumns.SIZE)) ?: 0
            val type =
                getStringOrNull(getColumnIndex(MediaStore.Video.VideoColumns.MIME_TYPE)) ?: ""
            val _id = getStringOrNull(getColumnIndex(MediaStore.Video.VideoColumns._ID)) ?: ""
            val duration = getIntOrNull(getColumnIndex(MediaStore.Video.VideoColumns.DURATION)) ?: 0
            if (size == 0) {
                continue
            }
            val videoData = VideoData(name, path, size, type, _id,duration)
            Log.i(TAG, videoData.toString())
            return videoData
        }
    }
    return null
}